package com.istock.union.user.service.impl;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;

import com.istock.base.enumration.Enums;
import com.istock.union.user.client.SSOClientUtils;
import com.istock.union.user.dao.MenuInfoMapper;
import com.istock.union.user.dao.RoleMenuInfoMapper;
import com.istock.union.user.dao.ext.ExtMenuInfoMapper;
import com.istock.union.user.model.Constants;
import com.istock.union.user.model.MenuInfo;
import com.istock.union.user.model.MenuInfoExample;
import com.istock.union.user.model.RoleInfo;
import com.istock.union.user.model.RoleMenuInfoExample;
import com.istock.union.user.model.ext.ExtMenuInfo;
import com.istock.union.user.model.ext.MenuInfoVO;
import com.istock.union.user.service.MenuInfoService;

@Repository
public class MenuInfoServiceImpl implements MenuInfoService{

	@Autowired
	private ExtMenuInfoMapper extMenuInfoMapper;
	@Autowired
	private MenuInfoMapper menuInfoMapper;
	
	@Autowired
	private RoleMenuInfoMapper roleMenuInfoMapper;
	
	/**使用当前的用户id,获得所有的用户菜单
	 * @param userId
	 * @return
	 */
	public List<MenuInfo> findMenuInfoByCredentialId(String credentialId){
		Map<String , Object> paramMap = new HashMap<String , Object>();
		paramMap.put("credentialId", credentialId);
		List<Integer> menuTypeList = new ArrayList<Integer>();
		menuTypeList.add(Enums.getInstance().getEnumsValueByCode("MENU_TYPE", "MENU_TYPE_DIC"));
		menuTypeList.add(Enums.getInstance().getEnumsValueByCode("MENU_TYPE", "MENU_TYPE_MENU"));
		paramMap.put("menuType", menuTypeList);
		return extMenuInfoMapper.findMenuByCredentialId(paramMap);
	}
	
	/**加载index,获得所有目录和菜单
	 * @return
	 */
	public List<MenuInfo> findAllMenu(){
		MenuInfoExample example = new MenuInfoExample();
		MenuInfoExample.Criteria criteria = example.createCriteria();
		
		criteria.andVisibleEqualTo(Constants.COMMON_VALID);
		criteria.andMenuTypeIn(Arrays.asList(new Integer[]{Constants.MENU_TYPE_DIC , Constants.MENU_TYPE_MENU}));
		
		example.setDistinct(true);
		example.setOrderByClause("PARENT_ID , ORDER_NUM");
		
		return menuInfoMapper.selectByExample(example);
	}
	
	/**菜单编辑,获得所有的资源
	 * @return
	 */
	public List<MenuInfo> findAllResource(){
		MenuInfoExample example = new MenuInfoExample();
//		MenuInfoExample.Criteria criteria = example.createCriteria();
		
//		criteria.andVisibleEqualTo(Constants.COMMON_VALID);
//		criteria.andMenuTypeIn(Arrays.asList(new Integer[]{Constants.MENU_TYPE_DIC , Constants.MENU_TYPE_MENU}));
//		example.setDistinct(true);
		example.setOrderByClause("PARENT_ID , ORDER_NUM");
		
		return menuInfoMapper.selectByExample(example);
	}
	
	/**用户权限标识获取
	 * @param userId
	 * @return
	 */
	public List<String> findPermByCredentialId(String credentialId){
		return extMenuInfoMapper.selectPermsByCredentialId(credentialId);
	}
	
	/**超级管理员获得所有的授权标识
	 * @return
	 */
	public List<String> findAllPerm(){
		return extMenuInfoMapper.selectAllPerms();
	}
	
	public List<MenuInfo> findButtonByParent(String parentId){
		MenuInfoExample example = new MenuInfoExample();
		MenuInfoExample.Criteria criteria = example.createCriteria();
		criteria.andParentIdEqualTo(parentId);
		example.setOrderByClause("ID , ORDER_NUM");
		
		return menuInfoMapper.selectByExample(example);
	}
	
	/**获得某一个菜单项的详细信息
	 * @param id
	 * @return
	 */
	public MenuInfoVO findMenuInfoById(String id){
		return extMenuInfoMapper.findMenuInfoById(id);
	}
	
	public List<Map<String, Object>> menuTreeData(boolean includeRoot)
    {
        List<Map<String, Object>> trees = new ArrayList<Map<String, Object>>();
        List<MenuInfo> menuList = findAllMenu();
        if(includeRoot) {
        	MenuInfo item = new MenuInfo();
        	item.setId("0");
        	item.setParentId("-1");
        	item.setMenuName("本系统");
        	menuList.add(item);
        }
        trees = getTrees(menuList, false, null, false);
        return trees;
    }
	
	public List<Map<String, Object>> menuTreeSelect(boolean includeRoot,List<String> checkedMenu)
    {
        List<Map<String, Object>> trees = new ArrayList<Map<String, Object>>();
        List<MenuInfo> menuList = findAllMenu();
        if(includeRoot) {
        	MenuInfo item = new MenuInfo();
        	item.setId("0");
        	item.setParentId("-1");
        	item.setMenuName("本系统");
        	menuList.add(item);
        }
        trees = getTrees(menuList, true, checkedMenu, false);
        return trees;
    }
	
	/**
	 * 
	 * @param roleInfo
	 * @return
	 */
	public List<Map<String, Object>> roleMenuTreeData(RoleInfo roleInfo , boolean includeButton) {
		String roleId = roleInfo.getId();
		List<Map<String, Object>> trees = new ArrayList<Map<String, Object>>(10);
		List<MenuInfo> menuList = null;
		if(includeButton) {
			menuList = findAllResource();
		}else {
			menuList = findAllMenu();
		}
		
		if (StringUtils.isNotBlank(roleId)) {
			List<String> roleMenuList = extMenuInfoMapper.selectMenuTree(roleId);
			trees = getTrees(menuList, true, roleMenuList, true);
		} else {
			trees = getTrees(menuList, false, null, true);
		}
		return trees;
	}
	
	/**
     * 对象转菜单树
     * 
     * @param menuList 菜单列表
     * @param isCheck 是否需要选中
     * @param roleMenuList 角色已存在菜单列表
     * @param permsFlag 是否需要显示权限标识
     * @return
     */
    public List<Map<String, Object>> getTrees(List<MenuInfo> menuList, boolean isCheck, List<String> roleMenuList,
            boolean permsFlag)
    {
        List<Map<String, Object>> trees = new ArrayList<Map<String, Object>>();
        for (MenuInfo menu : menuList)
        {
            Map<String, Object> menuItem = new HashMap<String, Object>();
            menuItem.put("id", menu.getId());
            menuItem.put("pId", menu.getParentId());
            menuItem.put("name", transMenuName(menu, roleMenuList, permsFlag));
            menuItem.put("title", menu.getMenuName());
            menuItem.put("type", menu.getMenuType());
            menuItem.put("value", menu.getId());
            if (isCheck && roleMenuList != null)
            {
//                deptMap.put("checked", roleMenuList.contains(menu.getId() + menu.getPerms()));
            	menuItem.put("checked", roleMenuList.contains(menu.getId()));
            }
            else
            {
            	menuItem.put("checked", false);
            }
            trees.add(menuItem);
        }
        return trees;
    }

    public String transMenuName(MenuInfo menu, List<String> roleMenuList, boolean permsFlag)
    {
        StringBuffer sb = new StringBuffer();
        sb.append(menu.getMenuName());
        if (permsFlag)
        {
            sb.append("<font color=\"#888\">&nbsp;&nbsp;&nbsp;" + menu.getPerms() + "</font>");
        }
        return sb.toString();
    }
    
    public Long findMenuCount(String id , String parentId , String menuName){
    	MenuInfoExample example = new MenuInfoExample();
		MenuInfoExample.Criteria criteria = example.createCriteria();
		if(StringUtils.isNotBlank(id)){
			criteria.andIdNotEqualTo(id);
		}
		if(StringUtils.isNotBlank(parentId)){
			criteria.andParentIdEqualTo(parentId);
		}
		if(StringUtils.isNotBlank(menuName)){
			criteria.andMenuNameEqualTo(menuName);
		}
		return menuInfoMapper.countByExample(example);
    }
    
    @Transactional
    public void saveMenuInfo(MenuInfo menuInfo){
    	if(menuInfo != null){
    		if(StringUtils.isNotBlank(menuInfo.getId())){
    			//update
    			menuInfo.setUpdateBy(SSOClientUtils.getInstance().findCurrentUser().getUserName());
    			menuInfo.setUpdateTime(new Date());
    			menuInfoMapper.updateByPrimaryKeySelective(menuInfo);
    		}else{
    			//insert
    			menuInfo.setCreateBy(SSOClientUtils.getInstance().findCurrentUser().getUserName());
    			menuInfo.setCreateTime(new Date());
    			menuInfoMapper.insertSelective(menuInfo);
    		}
    	}
    }
    
    /**
	 * 根据父菜单ID查看子菜单数量
	 * 
	 * @param id
	 * @return
	 */
	public long countMenusByParentId(String id) {
		MenuInfoExample example = new MenuInfoExample();
		example.createCriteria().andParentIdEqualTo(id);
		return menuInfoMapper.countByExample(example);
	}

	/**
	 * 根据菜单ID查看菜单被分配角色数量
	 * 
	 * @param menuId
	 * @return
	 */
	public long countRolesByMenuId(String menuId) {
		RoleMenuInfoExample example = new RoleMenuInfoExample();
		example.createCriteria().andMenuIdEqualTo(menuId);
		return roleMenuInfoMapper.countByExample(example);
	}

	/**
	 * 根据ID删除菜单
	 * 
	 * @param id
	 * @return
	 */
	public int deleteMenuById(String id) {
		return menuInfoMapper.deleteByPrimaryKey(id);
	}

	
	/**
	 * 菜单树生成(vue使用)
	 * @return
	 */
	public List<ExtMenuInfo> allMenuTreeNew() {
		return queryChildrenMenu("0");
	}

	private List<ExtMenuInfo> queryChildrenMenu(String parentId) {
		List<ExtMenuInfo> infos = new ArrayList<ExtMenuInfo>();
		List<MenuInfo> menuList = selectMenuListByParentId(parentId);
		if (CollectionUtils.isEmpty(menuList)) {
			return infos;
		}
		for (MenuInfo menuInfo :menuList) {
			ExtMenuInfo menuInfo1 = new ExtMenuInfo();
			menuInfo1.setId(menuInfo.getId());
			menuInfo1.setName(menuInfo.getMenuName());
			List<ExtMenuInfo> trees1 = this.queryChildrenMenu(menuInfo.getId());
			menuInfo1.setChildren(trees1);
			infos.add(menuInfo1);
		}
		return infos;
	}

	/**
	 * 当前角色的菜单树生成(vue使用)
	 * @param roleId
	 * @return
	 */
	public List<String> roleMenuTreeNew(String roleId) {
		return extMenuInfoMapper.selectMenuTree(roleId);
	}

	/**
	 * 查询菜单列表
	 */
	public List<MenuInfo> selectMenuListByParentId(String parentId) {
		MenuInfoExample example = new MenuInfoExample();
		MenuInfoExample.Criteria criteria = example.createCriteria();
		criteria.andParentIdEqualTo(parentId);
		example.setOrderByClause(" ORDER_NUM ASC, CREATE_TIME ASC");
		return menuInfoMapper.selectByExample(example);
	}
}
